<?php
/**
 * NOTICE OF LICENSE
 *
 * This source file is subject to the  Academic Free License (AFL 3.0)
 * that is available through the world-wide-web at this URL:
 * http://opensource.org/licenses/afl-3.0.php
 * If you did not receive a copy of the license and are unable to
 * obtain it through the world-wide-web, please send an email
 * to support@zprofess.com so we can send you a copy immediately.
 *
 * @category   	Prestashop module
 * @package		Review & Rating Synthesis
 * @version 	1.0.2
 * @author 		Rukan <rukanhitokiri@zprofess.com>
 * @copyright   Copyright (c) 2012 ZPROFESS. (http://www.zprofess.com)
 * @license    	http://opensource.org/licenses/afl-3.0.php  Academic Free License (AFL 3.0)
 */

class ZProductCriterion extends ObjectModel
{
	public		$id;
	public		$id_zproduct_criterion_type;
	public		$active = 1;
	public		$name;
	
	protected	$table = 'zproduct_criterion';
	protected	$identifier = 'id_zproduct_criterion';
	
	protected	$fieldsRequiredLang = array('name');
	protected	$fieldsSizeLang = array('name' => 128);
	protected	$fieldsValidateLang = array('name' => 'isGenericName');
	
	const CRITERION_TYPE_ALL_CATALOG 		= 1;
    const CRITERION_TYPE_SOME_CATEGORIES	= 2;
    const CRITERION_TYPE_SOME_PRODUCTS		= 3;
	
	/**
	 * Prepare fields for ObjectModel class (add, update)
	 * All fields are verified (pSQL, intval...)
	 * @view ObjectModel::getFields()
	 *
	 * @return array All object fields
	 */
	public function getFields()
	{
		parent::validateFields();
		$fields['id_zproduct_criterion_type'] = (int)$this->id_zproduct_criterion_type;
		$fields['active'] = (int)$this->active;
		return $fields;
	}
	
	/**
	 * Check then return multilingual fields for database interaction
	 *
	 * @return array Multilingual fields
	 */
	public function getTranslationsFieldsChild()
	{
		parent::validateFieldsLang();
		return parent::getTranslationsFields(array('name'));
	}
	
	/*********************
	 * BackOffice & Grid *
	 *********************/
	
	/**
	 * Return All Criterion Types
	 * 
	 * @return array All Criterion Types
	 */
	static public function getCriterionTypes()
	{
		return array(self::CRITERION_TYPE_ALL_CATALOG 		=> 'Valid for the entire catalog', 
					 self::CRITERION_TYPE_SOME_CATEGORIES 	=> 'Restricted to some categories', 
					 self::CRITERION_TYPE_SOME_PRODUCTS 	=> 'Restricted to some products');
	}
	
	/**
	 * Return Criterion Types
	 * 
     * @param int $id_zproduct_criterion_type
	 * @return string 	criterion Type
	 */
	static public function displayCriterionType($id_zproduct_criterion_type)
	{
		$options = self::getCriterionTypes();
    	return $options[$id_zproduct_criterion_type];
	}
	
	/***************
	 * FrontOffice *
	 ***************/
	
	/**
	 * Get All Criterion display by Product Id
	 * 
	 * @param int $id_product	current product id
	 * @param int $id_lang 		language id
	 * @return array 			criterion
	 */
	public static function getCriterionByProduct($id_product, $id_lang)
	{
		return Db::getInstance()->ExecuteS('
		SELECT zc.`id_zproduct_criterion`, zcl.`name`
		FROM `'._DB_PREFIX_.'zproduct_criterion` zc
		LEFT JOIN `'._DB_PREFIX_.'zproduct_criterion_lang` zcl ON (zc.id_zproduct_criterion = zcl.id_zproduct_criterion)
		LEFT JOIN `'._DB_PREFIX_.'zproduct_criterion_product` zcp ON (zc.`id_zproduct_criterion` = zcp.`id_zproduct_criterion` AND zcp.`id_product` = '.(int)$id_product.')
		LEFT JOIN `'._DB_PREFIX_.'zproduct_criterion_category` zcc ON (zc.`id_zproduct_criterion` = zcc.`id_zproduct_criterion`)
		LEFT JOIN `'._DB_PREFIX_.'product` p ON (p.id_category_default = zcc.id_category AND p.id_product = '.(int)$id_product.')
		WHERE zcl.`id_lang` = '.(int)($id_lang).' AND zc.active = 1 AND (zcp.id_product IS NOT NULL OR p.id_product IS NOT NULL OR zc.id_zproduct_criterion_type = 1)
		GROUP BY zc.id_zproduct_criterion');
	}
	
	/*********************
	 * BackOffice & Form *
	 *********************/

	/**
	 * Return categories Id associated with criterion
	 * 
	 * @return array
	 */
	public function getCategoriesId()
	{
		$result = Db::getInstance(_PS_USE_SQL_SLAVE_)->ExecuteS('
		SELECT zcc.id_category
		FROM `'._DB_PREFIX_.'zproduct_criterion_category` zcc
		WHERE zcc.id_zproduct_criterion = '.(int)$this->id);
		
		$categoriesId = array();
		foreach ($result AS $row)
			$categoriesId[] = (int)$row['id_category'];
		return $categoriesId;
	}
	
	/**
	 * Add categories associated with criterion
	 * 
	 * @return boolean Add result
	 */
	public function addCategories($categories)
	{
		$result = true;
		$result = $this->_cleanCategories();
		foreach ($categories as $category) {
			$row = array('id_zproduct_criterion' => (int)$this->id, 
						 'id_category' => (int)$category);
			Db::getInstance()->AutoExecute(_DB_PREFIX_.'zproduct_criterion_category', $row, 'INSERT');
		}
		return $result;
	}
	
	/**
	 * Delete categories associated with criterion
	 *
	 * @return boolean Deletion result
	 */
	private function _cleanCategories($id = null) 
	{
		$id = is_null($id) ? (int)$this->id : $id;
		return Db::getInstance()->Execute('DELETE FROM `'._DB_PREFIX_.'zproduct_criterion_category` 
											WHERE `id_zproduct_criterion` = '.$id);
	}
	
	/**
	 * Return products Id associated with criterion
	 * 
	 * @return products
	 */
	public function getProductsId()
	{
		global $cookie;
		if (!$this->id)
			return array();
		$result = Db::getInstance(_PS_USE_SQL_SLAVE_)->ExecuteS('
		SELECT pl.id_product
		FROM `'._DB_PREFIX_.'product` p
		LEFT JOIN `'._DB_PREFIX_.'product_lang` pl ON p.id_product = pl.id_product
		WHERE pl.id_lang = '.(int)$cookie->id_lang
		.($this->id ? (' AND p.id_product IN (SELECT zcp.id_product FROM `'._DB_PREFIX_.'zproduct_criterion_product` zcp WHERE zcp.id_zproduct_criterion = '.(int)$this->id.')') : '').'
		ORDER BY pl.name');
		
		$productsId = array();
		foreach ($result AS $row)
			$productsId[] = (int)$row['id_product'];
		return $productsId;
	}
		
	/**
	 * Add product associated with criterion
	 * 
	 * @return boolean Add result
	 */
	public function addProducts($products)
	{
		$result = true;
		$result = $this->_cleanProducts();
		foreach ($products as $product) {
			$row = array('id_zproduct_criterion' => (int)$this->id, 
						 'id_product' => (int)$product);
			Db::getInstance()->AutoExecute(_DB_PREFIX_.'zproduct_criterion_product', $row, 'INSERT');
		}
		return $result;
	}
	
	/**
	 * Delete products associated with criterion
	 * 
	 * @return boolean Deletion result
	 */
	private function _cleanProducts($id = null) 
	{
		$id = is_null($id) ? (int)$this->id : $id;
		return Db::getInstance()->Execute('DELETE FROM '._DB_PREFIX_.'zproduct_criterion_product 
										  	WHERE id_zproduct_criterion = '.$id);
	}
	
	/**
	 * Delete categories, products associated with criterion
	 * 
	 * @return boolean Deletion result
	 */
	public function deleteAssociated($id = null)
	{
		if($this->_cleanCategories($id) AND $this->_cleanProducts($id))
			return true;
		return false;
	}
}